package com.jt808.decode.utils;

import com.jt808.decode.constant.*;
import com.jt808.decode.model.Jt808Message;
import com.jt808.decode.model.Location;
import com.jt808.decode.model.SensorAlarmDescribe;
import io.netty.buffer.ByteBuf;
import io.netty.buffer.ByteBufUtil;
import lombok.extern.slf4j.Slf4j;

import java.time.ZonedDateTime;
import java.time.format.DateTimeFormatter;
import java.util.*;

/**
 * Positioning data analysis
 * @date 2023-03-03
 */
@Slf4j
public class Message0200Parser {
    /**
     * decoding location information
     *
     * @param msgBody
     * @return
     */
    public static Location parse(Jt808Message msg, ByteBuf msgBody) throws Exception {
        //Processing location information
        Location location = parseLocation(msgBody);
        location.setDeviceId(msg.getDeviceId());
        location.setHexMsgId(NumberUtil.formatMessageId(msg.getMsgId()));
        location.setMsgFlowId(msg.getMsgFlowId());
        //Processing additional information
        if (msgBody.readableBytes() > 0) {
            parseExtraInfo(msgBody, location);
        }
        return location;
    }

    /**
     * Processing location information
     *
     * @param msgBody
     * @return
     */
    private static Location parseLocation(ByteBuf msgBody) {
        //alarm flag
        long alarmFlag = msgBody.readUnsignedInt();
        //terminal status
        long status = msgBody.readUnsignedInt();
        //lat
        double lat = NumberUtil.multiply(msgBody.readUnsignedInt(), NumberUtil.COORDINATE_PRECISION);
        //lon
        double lon = NumberUtil.multiply(msgBody.readUnsignedInt(), NumberUtil.COORDINATE_PRECISION);
        //altitude,unit: m
        int altitude = msgBody.readUnsignedShort();
        //speed ,unit: km/h
        double speed = NumberUtil.multiply(msgBody.readUnsignedShort(), NumberUtil.ONE_PRECISION);
        //direction (0~360;0:north)
        int direction = msgBody.readShort();
        //gnss time
        byte[] timeArr = new byte[6];
        msgBody.readBytes(timeArr);
        String bcdTimeStr = ByteBufUtil.hexDump(timeArr);
        ZonedDateTime gpsZonedDateTime = CommonUtil.parseBcdTime(bcdTimeStr);
        //Judge whether the south latitude and west longitude are based on the value of the status bit
        if (NumberUtil.getBitValue(status, 2) == 1) {
            lat = -lat;
        }
        if (NumberUtil.getBitValue(status, 3) == 1) {
            lon = -lon;
        }
        //location package package
        Location location = new Location();
        location.setLocationType((status & 0x0002) > 0 ? 1 : 0);
        location.setLat(lat);
        location.setLon(lon);
        location.setAltitude(altitude);
        location.setSpeed(speed);
        location.setDirection(direction);
        DateTimeFormatter formatter = DateTimeFormatter.ISO_ZONED_DATE_TIME;
        location.setTime(formatter.format(gpsZonedDateTime));
        //parse status
        Map<String,Integer> statusMap = parseJt808Status(status);
        location.setStatusMap(statusMap);
        return location;
    }

    /**
     * Processing additional information
     * @param msgBody
     * @param location
     * @throws Exception
     */
    private static void parseExtraInfo(ByteBuf msgBody, Location location) throws Exception {
        //Additional information
        Map<String,Object> expandMap=new HashMap<>();
        Map<String, Integer> statusMap =new HashMap<>();
        if(location.getStatusMap()!=null&&location.getStatusMap().size()>0) {
            statusMap = location.getStatusMap();
        }
        ByteBuf extraInfoBuf = null;
        while (msgBody.readableBytes() > 1) {
            int extraInfoId = msgBody.readUnsignedByte();
            int extraInfoLen = msgBody.readUnsignedByte();
            if (msgBody.readableBytes() < extraInfoLen) {
                break;
            }
            extraInfoBuf = msgBody.readSlice(extraInfoLen);
            if(extraInfoBuf.readableBytes()==0){
                continue;
            }
            switch (extraInfoId) {
                //mileage,unit: km
                case 0x01:
                    double mileage = NumberUtil.multiply(extraInfoBuf.readUnsignedInt(), NumberUtil.ONE_PRECISION);
                    location.setMileage(mileage);
                    break;
                //fuel
                case 0x02:
                    double fuel = NumberUtil.multiply(extraInfoBuf.readUnsignedShort(), NumberUtil.ONE_PRECISION);
                    expandMap.put(Jt808ExpandConstant.FUEL,fuel);
                    break;
                //tachograph speed
                case 0x03:
                    double recoderSpeed = NumberUtil.multiply(extraInfoBuf.readUnsignedShort(), NumberUtil.ONE_PRECISION);
                    expandMap.put(Jt808ExpandConstant.RECODER_SPEED,recoderSpeed);
                    break;
                //ID of alarm event requiring manual confirmation
                case 0x04:
                    int alarmEventId = extraInfoBuf.readUnsignedShort();
                    expandMap.put(Jt808ExpandConstant.RESPONSE_EVENT,alarmEventId);
                    break;
                //tyre
                case 0x05:
                    String tyres="";
                    while (extraInfoBuf.readableBytes()>0) {
                        int tyre=extraInfoBuf.readUnsignedByte();
                        if(tyre==0xff) {
                            continue;
                        } else {
                            tyres += tyre+";";
                        }
                    }
                    expandMap.put(Jt808ExpandConstant.TYRE,tyres);
                    break;
                //Temperature in the compartment
                case 0x06:
                    expandMap.put(Jt808ExpandConstant.CARRIAGE_TEMPERATURE,extraInfoBuf.readShort());
                    break;
                //Extended vehicle signal status bit
                case 0x25:
                    long signal_status = extraInfoBuf.readUnsignedInt();
                    List<Integer> signal_statusArr = NumberUtil.parseIntegerBits(signal_status);
                    expandMap.put(Jt808ExpandConstant.SIGNAL_STATUS, signal_statusArr);
                    break;
                //IO status bit
                case 0x2A:
                    int io_status = extraInfoBuf.readUnsignedShort();
                    List<Integer> io_statusArr = NumberUtil.parseShortBits(io_status);
                    expandMap.put(Jt808ExpandConstant.IO_STATUS, io_statusArr);
                    break;
                //AD
                case 0x2B:
                    int AD0 = extraInfoBuf.readUnsignedShort();
                    int AD1 = extraInfoBuf.readUnsignedShort();
                    List<Integer> ADArr=new ArrayList<>();
                    ADArr.add(AD0);
                    ADArr.add(AD1);
                    expandMap.put(Jt808ExpandConstant.ANALOG_QUANTITY, ADArr);
                    break;
                //Signal strength of wireless communication network
                case 0x30:
                    int gsmSignal=extraInfoBuf.readUnsignedByte();
                    location.setNetworkSignal(gsmSignal);
                    break;
                //Number of GNSS positioning satellites
                case 0x31:
                    int gnssSignal=extraInfoBuf.readUnsignedByte();
                    location.setGnssNum(gnssSignal);
                    break;
                //cells information
                case 0xF0:
                    List<String>lbsCells=new LinkedList<>();
                    while (extraInfoBuf.readableBytes()>11) {
                        int mcc = 0;
                        int mnc = 0;
                        if (extraInfoBuf.readableBytes() % 0x0C > 0) {
                            mcc = extraInfoBuf.readUnsignedShort();
                            mnc = extraInfoBuf.readUnsignedShort();
                        } else {
                            mcc = extraInfoBuf.readUnsignedShort();
                            mnc = extraInfoBuf.readUnsignedByte();
                        }
                        //ci
                        long ci = extraInfoBuf.readUnsignedInt();
                        //lac
                        long lac = extraInfoBuf.readUnsignedInt();
                        //RSSI
                        int rssi = extraInfoBuf.readByte();
                        String lbsCell=String.format("%s,%s,%s,%s,%s", mcc, mnc, lac,ci,rssi);
                        lbsCells.add(lbsCell);
                    }
                    location.setLbsCells(lbsCells);
                    break;
                case 0xF1:
                    long voltageF1=extraInfoBuf.readUnsignedInt();
                    if(voltageF1>0) {
                        expandMap.put(Jt808ExpandConstant.EXTERNAL_VOLTAGE, String.format("%.2f",voltageF1 * 0.001));
                        statusMap.put(Jt808StatusConstant.POWERED,1);
                    }else{
                        statusMap.put(Jt808StatusConstant.POWERED,0);
                    }
                    break;
                case 0xF2:
                    byte [] f2Arr= new byte[extraInfoBuf.readableBytes()];
                    extraInfoBuf.readBytes(f2Arr);
                    expandMap.put(Jt808ExpandConstant.SOFTWARE_VERSION, new String(f2Arr));
                    break;
                case 0xF3:
                    expandMap.put(Jt808ExpandConstant.BLUETOOTH, parseAovxF3(extraInfoBuf));
                    break;
                case 0xF4:
                    expandMap.put(Jt808ExpandConstant.WIFI, parseAovxF4(extraInfoBuf));
                    break;
                case 0xF5:
                    expandMap.put(Jt808ExpandConstant.GPIO, parseAovxF5(extraInfoBuf));
                    break;
                case 0xF6:
                    List<Map<String,Object>> sensorList=parseAovxF6(location,expandMap,extraInfoBuf,statusMap);
                    if(sensorList==null) {
                        break;
                    }
                    expandMap.put(Jt808ExpandConstant.SENSOR, sensorList);
                    break;
                case 0xF7:
                    parseAovxF7(location,expandMap,extraInfoBuf);
                    break;
                case 0xF8:
                    Map<String,Object> deviceMap = parseAovxF8(extraInfoBuf);
                    if(deviceMap==null) {
                        break;
                    }
                    expandMap.put(Jt808ExpandConstant.DEVICE, deviceMap);
                    break;
                case 0xF9:
                    Map<String,Object> auxiliaryMap = parseAovxF9(extraInfoBuf,expandMap);
                    if(auxiliaryMap==null) {
                        break;
                    }
                    expandMap.put(Jt808ExpandConstant.AUXILIARY, auxiliaryMap);
                    break;
                default:
                    break;
            }
        }
        location.setExpandMap(expandMap);
        location.setStatusMap(statusMap);
    }

    /**
     * decode alarm
     *
     * @param alarmFlag
     * @return
     */
    private static List<String> parseJt808Alarm(long alarmFlag) {
        List<String> alarmTypeList = new ArrayList<>();
        for (int i = 0; i < 32; i++) {
            if (NumberUtil.getBitValue(alarmFlag, i) == 1) {
                try {
                    AlarmTypeEnum alarmType = AlarmTypeEnum.valueOf("ALARM_" + i);
                    alarmTypeList.add(alarmType.getDesc());
                } catch (Exception e) {
                }
            }
        }
        return alarmTypeList;
    }

    /**
     * decode status
     * @param status
     * @return
     */
    private static Map<String,Integer> parseJt808Status(long status) {
        Map<String,Integer> statusMap=new HashMap<>();
        statusMap.put(Jt808StatusConstant.REALTIME_DATA,NumberUtil.getBitValue(status,31));
        return statusMap;
    }

    /**
     * BLE information
     * @param extraInfoBuf
     * @return
     */
    private static List<Map<String,Object>> parseAovxF3(ByteBuf extraInfoBuf){
        try{
            int mark=extraInfoBuf.readByte();
            List<Map<String, Object>> bluetoothList = new ArrayList<>();
            while (extraInfoBuf.readableBytes() > 6) {
                Map<String, Object> bleMap = new HashMap<>();
                byte [] macArr= new byte[6];
                extraInfoBuf.readBytes(macArr);
                bleMap.put(BluetoothConstant.MAC, CommonUtil.handleMacAddress(ByteBufUtil.hexDump(macArr)));
                bleMap.put(BluetoothConstant.RSSI, extraInfoBuf.readByte());
                if ((mark & 0x01) > 0) {
                    byte[] nameArr = new byte[10];
                    extraInfoBuf.readBytes(nameArr);
                    bleMap.put(BluetoothConstant.NAME, new String(nameArr));
                }
                if ((mark & 0x02) > 0) {
                    bleMap.put(BluetoothConstant.FWVER, extraInfoBuf.readUnsignedShort());
                }
                if ((mark & 0x04) > 0) {
                    bleMap.put(BluetoothConstant.VOLTAGE, String.format("%.3f",extraInfoBuf.readUnsignedShort() * 0.001));
                }
                if ((mark & 0x08) > 0) {
                    String temperature = String.format("%.1f",CommonUtil.parseTemperature(extraInfoBuf.readShort()));
                    if(!temperature.equals("-1000.0")) {
                        bleMap.put(BluetoothConstant.TEMPERATURE, temperature);
                    }
                }
                if ((mark & 0x10) > 0) {
                    bleMap.put(BluetoothConstant.HUMIDITY, String.format("%.1f",extraInfoBuf.readUnsignedShort() * 0.1));
                }
                if ((mark & 0x20) > 0) {
                    int x = extraInfoBuf.readUnsignedShort();
                    int y = extraInfoBuf.readUnsignedShort();
                    int z = extraInfoBuf.readUnsignedShort();
                    x = x > 32768 ? (x - 65536) : x;
                    y = y > 32768 ? (y - 65536) : y;
                    z = z > 32768 ? (z - 65536) : z;
                    bleMap.put(BluetoothConstant.SENSOR, String.format("x:%s,y:%s,z:%s", x, y, z));
                }
                if ((mark & 0x40) > 0) {
                    extraInfoBuf.readUnsignedShort();
                }
                if ((mark & 0x80) > 0) {
                    extraInfoBuf.readUnsignedShort();
                }
                bluetoothList.add(bleMap);
            }
            return bluetoothList;
        }catch (Exception e){
            log.error("parseAovxF3 method exception:",e);
            return null;
        }
    }

    /**
     * WIFI information
     * @param extraInfoBuf
     * @return
     */
    private static List<Map<String,Object>> parseAovxF4(ByteBuf extraInfoBuf){
        try{
            //屏蔽字
            List<Map<String, Object>> wifiList = new ArrayList<>();
            while (extraInfoBuf.readableBytes() > 6) {
                Map<String, Object> wifiMap = new HashMap<>();
                byte [] macArr= new byte[6];
                extraInfoBuf.readBytes(macArr);
                wifiMap.put(BluetoothConstant.MAC, CommonUtil.handleMacAddress(ByteBufUtil.hexDump(macArr)));
                wifiMap.put(BluetoothConstant.RSSI, extraInfoBuf.readByte());
                wifiList.add(wifiMap);
            }
            return wifiList;
        }catch (Exception e){
            log.error("parseAovxF4 method exception:",e);
            return null;
        }
    }

    /**
     * GPIO information
     * @param extraInfoBuf
     * @return
     */
    private static Map<String,List<String>> parseAovxF5(ByteBuf extraInfoBuf){
        try{
            Map<String,List<String>> gpio=new HashMap<>();
            byte[] channelArr=new byte[4];
            extraInfoBuf.readBytes(channelArr);
            String hexChannel=ByteBufUtil.hexDump(channelArr);
            List<String> gpioStatus=new ArrayList<>();
            while (extraInfoBuf.readableBytes() > 3) {
                byte[] statusArr=new byte[4];
                extraInfoBuf.readBytes(statusArr);
                gpioStatus.add(ByteBufUtil.hexDump(statusArr));
            }
            gpio.put(hexChannel,gpioStatus);
            return gpio;
        }catch (Exception e){
            log.error("parseAovxF5 method exception:",e);
            return null;
        }
    }

    /**
     * Sensor information
     * @param extraInfoBuf
     * @param expandMap
     * @return
     */
    private static List<Map<String,Object>> parseAovxF6(Location location,Map<String,Object> expandMap,ByteBuf extraInfoBuf,Map<String,Integer> statusMap){
        try{
            List<Map<String, Object>> sensorList = new ArrayList<>();
            while (extraInfoBuf.readableBytes() > 2) {
                Map<String, Object> sensorMap=new HashMap<>();
                int dataType = extraInfoBuf.readUnsignedByte();
                int maskF6 = extraInfoBuf.readUnsignedByte();
                sensorMap.put(SensorConstant.DATA_TYPE, dataType);
                if ((maskF6 & 0x01) > 0) {
                    int light = extraInfoBuf.readUnsignedShort();
                    sensorMap.put(SensorConstant.LIGHT, light);
                }
                if ((maskF6 & 0x02) > 0) {
                    //temperature
                    String temperature = String.format("%.1f",CommonUtil.parseTemperature(extraInfoBuf.readShort()));
                    if(!temperature.equals("-1000.0")) {
                        sensorMap.put(SensorConstant.TEMPERATURE, temperature);
                    }
                }
                if ((maskF6 & 0x04) > 0) {
                    //humidity
                    int humidity = extraInfoBuf.readUnsignedShort();
                    sensorMap.put(SensorConstant.HUMIDITY, String.format("%.1f",humidity * 0.1));
                }
                if ((maskF6 & 0x08) > 0) {
                    //Accelerometer
                    int x = extraInfoBuf.readUnsignedShort();
                    int y = extraInfoBuf.readUnsignedShort();
                    int z = extraInfoBuf.readUnsignedShort();
                    x = x > 32768 ? (x - 65536) : x;
                    y = y > 32768 ? (y - 65536) : y;
                    z = z > 32768 ? (z - 65536) : z;
                    sensorMap.put(SensorConstant.ACCELEROMETER, String.format("x:%s,y:%s,z:%s", x, y, z));
                }
                if ((maskF6 & 0x10) > 0) {
                    //Alarm information
                    int light_Limit = extraInfoBuf.readUnsignedShort();
                    sensorMap.put(SensorConstant.LIGHT_LIMIT, light_Limit);
                    double temp_Max = extraInfoBuf.readShort();
                    sensorMap.put(SensorConstant.TEMP_MAX,String.format("%.1f",temp_Max));
                    double temp_Min = extraInfoBuf.readShort();
                    sensorMap.put(SensorConstant.TEMP_MIN,String.format("%.1f",temp_Min));
                    int hum_Max = extraInfoBuf.readUnsignedShort();
                    sensorMap.put(SensorConstant.HUM_MAX,hum_Max);
                    int hum_Min = extraInfoBuf.readUnsignedShort();
                    sensorMap.put(SensorConstant.HUM_MIN,hum_Min);
                    if (sensorMap.containsKey(SensorConstant.LIGHT)) {
                        int light = Integer.parseInt(sensorMap.get(SensorConstant.LIGHT).toString());
                        //Judge light alarm
                        if ((maskF6 & 0x01) > 0 && light > light_Limit) {
                            SensorAlarmDescribe describe = new SensorAlarmDescribe();
                            describe.setType("5");
                            describe.setCurrent(String.valueOf(light));
                            describe.setThreshold(String.valueOf(light_Limit));
                            expandMap.put(Jt808ExpandConstant.LIGHT_ALARM_DESCRIBE, describe);
                        }
                    }
                    if (sensorMap.containsKey(SensorConstant.TEMPERATURE)) {
                        double temperature = Double.parseDouble(sensorMap.get(SensorConstant.TEMPERATURE).toString());
                        //Judge temperature alarm
                        if ((maskF6 & 0x02) > 0 && (temperature > temp_Max || temperature < temp_Min)) {
                            SensorAlarmDescribe describe = new SensorAlarmDescribe();
                            if (temperature > temp_Max) {
                                describe.setType("1");
                                describe.setCurrent(String.format("%.1f",temperature));
                                describe.setThreshold(String.format("%.1f",temp_Max));
                            }
                            else {
                                describe.setType("2");
                                describe.setCurrent(String.format("%.1f",temperature));
                                describe.setThreshold(String.format("%.1f",temp_Max));
                            }
                            expandMap.put(Jt808ExpandConstant.TEMP_ALARM_DESCRIBE, describe);
                        }
                    }
                    if (sensorMap.containsKey(SensorConstant.HUMIDITY)) {
                        double humidity = Double.parseDouble(sensorMap.get(SensorConstant.HUMIDITY).toString());
                        //Judge humidity alarm
                        if ((maskF6 & 0x04) > 0 && (humidity > hum_Max || humidity < hum_Min)) {
                            SensorAlarmDescribe describe = new SensorAlarmDescribe();
                            if (humidity > hum_Max) {
                                describe.setType("3");
                                describe.setCurrent(String.format("%.1f",humidity));
                                describe.setThreshold(String.valueOf(hum_Max));
                            } else {
                                describe.setType("4");
                                describe.setCurrent(String.format("%.1f",humidity));
                                describe.setThreshold(String.valueOf(hum_Min));
                            }
                            expandMap.put(Jt808ExpandConstant.TEMP_ALARM_DESCRIBE, describe);
                        }
                    }
                }
                //pressure
                if ((maskF6 & 0x20) > 0){
                    Integer pressure = extraInfoBuf.readUnsignedShort()*100;
                    sensorMap.put(SensorConstant.PRESSURE,pressure);
                }
                //Res2
                if ((maskF6 & 0x40) > 0){
                    extraInfoBuf.readShort();
                }
                //Res3
                if ((maskF6 & 0x80) > 0){
                    extraInfoBuf.readShort();
                }
                sensorList.add(sensorMap);
            }
            return sensorList;
        }catch (Exception e){
            log.error("parseAovxF6 method exception:",e);
            return null;
        }
    }

    /**
     * Battery information
     * @param location
     * @param expandMap
     * @param extraInfoBuf
     * @return
     */
    private static void parseAovxF7(Location location, Map<String,Object> expandMap, ByteBuf extraInfoBuf) {
        try{
            if(extraInfoBuf.readableBytes()>3) {
                double voltage = extraInfoBuf.readUnsignedInt() * 0.001;
                location.setVoltage(voltage);
            }
            if(extraInfoBuf.readableBytes()>0) {
                int chargeStatus = extraInfoBuf.readByte();
                expandMap.put(Jt808ExpandConstant.BATTERY_CHARGE, chargeStatus);
            }
            if(extraInfoBuf.readableBytes()>0) {
                int battery = extraInfoBuf.readUnsignedByte();
                location.setBattery(battery);
            }
        }catch (Exception e){
            log.error("parseAovxF7 method exception:",e);
        }
    }

    /**
     * device information
     * @param extraInfoBuf
     * @return
     */
    private static Map<String,Object> parseAovxF8(ByteBuf extraInfoBuf){
        try{
            Map<String,Object> device=new HashMap<>();
            int workModel=extraInfoBuf.readUnsignedByte();
            byte[] imeiArr=new byte[8];
            extraInfoBuf.readBytes(imeiArr);
            byte[] iccidArr=new byte[10];
            extraInfoBuf.readBytes(iccidArr);
            byte[] deviceTypeArr=new byte[10];
            extraInfoBuf.readBytes(deviceTypeArr);
            device.put(DeviceConstant.WORK_MODEL,workModel);
            device.put(DeviceConstant.IMEI, ByteBufUtil.hexDump(imeiArr));
            device.put(DeviceConstant.ICCID,ByteBufUtil.hexDump(iccidArr));
            device.put(DeviceConstant.DEVICE_TYPE,new String(deviceTypeArr));
            return device;
        }catch (Exception e){
            log.error("parseAovxF8 method exception:",e);
            return null;
        }
    }

    /**
     * expand information
     * @param extraInfoBuf
     * @return
     */
    private static Map<String,Object> parseAovxF9(ByteBuf extraInfoBuf,Map<String,Object> expandMap){
        try{
            int mask = extraInfoBuf.readUnsignedShort();
            Map<String,Object> auxiliary=new HashMap<>();
            if((mask&0x01)>0){
                auxiliary.put(AuxiliaryConstant.POSITION_AGE,extraInfoBuf.readUnsignedInt());
            }
            if((mask&0x02)>0){
                auxiliary.put(AuxiliaryConstant.ACC_DURATION,extraInfoBuf.readUnsignedInt());
            }
            if((mask&0x04)>0){
                auxiliary.put(AuxiliaryConstant.HDOP,extraInfoBuf.readUnsignedShort());
            }
            if((mask&0x08)>0){
                //gnss time
                byte[] timeArr = new byte[6];
                extraInfoBuf.readBytes(timeArr);
                String bcdTimeStr = ByteBufUtil.hexDump(timeArr);
                auxiliary.put(AuxiliaryConstant.GNSS_TIME,bcdTimeStr);
            }
            if((mask&0x20)>0){
                auxiliary.put(AuxiliaryConstant.SAMPLE_TIME,extraInfoBuf.readUnsignedInt());
                auxiliary.put(AuxiliaryConstant.REPORT_TIME,extraInfoBuf.readUnsignedInt());
            }
            if((mask&0x40)>0){
                Integer extendTempMark=extraInfoBuf.readUnsignedShort();
                if((extendTempMark&0x01)>0){
                    String ext_temp = String.format("%.1f",CommonUtil.parseTemperature(extraInfoBuf.readShort()));
                    if(!ext_temp.equals("-1000.0")) {
                        auxiliary.put(AuxiliaryConstant.EXT_TEMP, ext_temp);
                    }
                    double ext_temp_max=extraInfoBuf.readShort();
                    auxiliary.put(AuxiliaryConstant.EXT_TEMP_MAX, String.format("%.1f",ext_temp_max));
                    double ext_temp_min = extraInfoBuf.readShort();
                    auxiliary.put(AuxiliaryConstant.EXT_TEMP_MIN, String.format("%.1f",ext_temp_min));
                    if(auxiliary.containsKey(AuxiliaryConstant.EXT_TEMP)&&auxiliary.containsKey(AuxiliaryConstant.EXT_TEMP_MAX)&&auxiliary.containsKey(AuxiliaryConstant.EXT_TEMP_MIN)){
                        SensorAlarmDescribe describe = new SensorAlarmDescribe();
                        if (Double.parseDouble(ext_temp) > ext_temp_max) {
                            describe.setType("1");
                            describe.setCurrent(ext_temp);
                            describe.setThreshold(String.format("%.1f",ext_temp_max));
                        }
                        else {
                            describe.setType("2");
                            describe.setCurrent(ext_temp);
                            describe.setThreshold(String.format("%.1f",ext_temp_min));
                        }
                        expandMap.put(Jt808ExpandConstant.EXT_TEMP_ALARM_DESCRIBE, describe);
                    }
                }
            }
            return auxiliary;
        }catch (Exception e){
            log.error("parseAovxF9 method exception:",e);
            return null;
        }
    }
}
